package exam_ctrl

import (
	"net/http"
	"ubt-aio-service/app/mod/exam_mod"
	"ubt-aio-service/app/mod/sys_mod"
	"ubt-aio-service/app/pkg/parse"
	"ubt-aio-service/app/serv/exam_serv"
	"ubt-aio-service/app/serv/sys_serv"
	"ubt-aio-service/app/utils"
)

type quest struct{}

var QstCtrl quest

// Save 保存
func (c *quest) Save(r *http.Request, w http.ResponseWriter) {
	// 通过头部请求的token获取用户信息
	token := r.Header.Get(utils.Token)
	userInfo := sys_serv.GetUserInfo(token)
	if userInfo == nil {
		utils.ToJson(w, utils.NoLogin)
		return
	}
	userId := userInfo.UserId
	req := &exam_mod.QstSaveReq{}
	// 将请求的参数转换为请求结构体
	if err := parse.Parse(r, req); err != "" {
		utils.ToJson(w, &utils.ResJson{Code: utils.ParamErr.Code, Msg: err})
		return
	}
	// 过滤关键参数值中的非法字符
	req.QstId = utils.InputFilter(req.QstId, true)
	req.Title = utils.InputFilter(req.Title, true)
	req.QstNo = utils.InputFilter(req.QstNo, true)
	// 判断编码是否重复
	extVo := &exam_mod.QstExtVo{Title: req.Title, QstNo: req.QstNo, Kind: req.Kind, QstId: req.QstId}
	if ext := exam_serv.QstServ.Exists(extVo); ext {
		utils.ToJson(w, utils.Exists)
		return
	}
	var (
		res  *utils.ResJson
		kind uint8
		ch   = make(chan int)
	)
	if req.SaveType == 1 {
		// 新增
		res = exam_serv.QstServ.Add(req)
		go exam_serv.QstServ.AddOpts(ch, req.OptList)
		ch <- 1
		kind = 1
	} else {
		// 修改
		res = exam_serv.QstServ.Update(req)
		go exam_serv.QstServ.DelOptByQst(ch, req.QstId)
		ch <- 1
		go exam_serv.QstServ.AddOpts(ch, req.OptList)
		ch <- 2
		kind = 3
	}
	if res.Code == utils.Succeed.Code {
		//go exam_serv.QstServ.CacheOpts(ch)
		//ch <- 3
		logReq := &sys_mod.SysLogSaveReq{UserId: userId, MenuCode: utils.ExamBase, IpAddr: userInfo.ClientIp, Kind: kind}
		sys_serv.SysLogServ.Add(logReq)
	}
	utils.ToJson(w, res)
}

// Deletes 删除
func (c *quest) Deletes(r *http.Request, w http.ResponseWriter) {
	// 通过头部请求的token获取用户信息
	token := r.Header.Get(utils.Token)
	userInfo := sys_serv.GetUserInfo(token)
	if userInfo == nil {
		utils.ToJson(w, utils.NoLogin)
		return
	}
	req := &exam_mod.QstDelsReq{}
	// 将请求的参数转换为请求结构体
	if err := parse.Parse(r, req); err != "" {
		utils.ToJson(w, &utils.ResJson{Code: utils.ParamErr.Code, Msg: err})
		return
	}
	// 过滤关键参数值中的非法字符
	req.Ids = utils.InputFilter(req.Ids, true)
	res := exam_serv.QstServ.Deletes(req.Ids)
	if res.Code == utils.Succeed.Code {
		ch := make(chan int)
		go exam_serv.QstServ.DelOptsByQst(ch, req.Ids)
		ch <- 1
		logReq := &sys_mod.SysLogSaveReq{UserId: userInfo.UserId, MenuCode: utils.ExamBase, IpAddr: userInfo.ClientIp, Kind: 2}
		sys_serv.SysLogServ.Add(logReq)
	}
	utils.ToJson(w, res)
}

// One 获取详情
func (c *quest) One(r *http.Request, w http.ResponseWriter) {
	// 通过头部请求的token获取用户信息
	token := r.Header.Get(utils.Token)
	userInfo := sys_serv.GetUserInfo(token)
	if userInfo == nil {
		utils.ToJson(w, utils.NoLogin)
		return
	}
	// 过滤关键参数值中的非法字符
	u := r.URL.Query()
	if u == nil {
		utils.ToJson(w, utils.ParamErr)
		return
	}
	qstId := u.Get("qstId")
	// 过滤关键参数值中的非法字符
	qstId = utils.InputFilter(qstId, true)
	if qstId == "" || len(qstId) != 21 {
		utils.ToJson(w, utils.ParamErr)
		return
	}
	res := exam_serv.QstServ.One(qstId)
	if res.Code == utils.Succeed.Code {
		optRes := exam_serv.QstServ.List(qstId)
		res.Data.(map[string]any)["optList"] = optRes.Data
	}
	utils.ToJson(w, res)
}

// Page 获取分页列表
func (c *quest) Page(r *http.Request, w http.ResponseWriter) {
	// 通过头部请求的token获取用户信息
	token := r.Header.Get(utils.Token)
	userInfo := sys_serv.GetUserInfo(token)
	if userInfo == nil {
		utils.ToJson(w, utils.NoLogin)
		return
	}
	// 过滤关键参数值中的非法字符
	u := r.URL.Query()
	if u == nil {
		utils.ToJson(w, utils.ParamErr)
		return
	}
	keywords := u.Get("keywords")
	kinds := u.Get("kind")
	limits := u.Get("limit")
	offsets := u.Get("offset")
	keywords = utils.InputFilter(keywords, false)
	kinds = utils.InputFilter(kinds, true)
	limits = utils.InputFilter(limits, true)
	offsets = utils.InputFilter(offsets, true)
	kind := parse.Str2u8(kinds)
	limit := parse.Str2u8(limits)
	offset := parse.Str2u32(offsets)
	// 先统计信息的数量
	req := &exam_mod.QstPageReq{Keywords: keywords, Kind: kind}
	res := exam_serv.QstServ.Count(req)
	if res.Code == utils.Succeed.Code {
		dto := &exam_mod.QstPageRes{Total: res.Data.(map[string]any)["nums"].(int64)}
		// 再查询具体的信息列表
		req.Limit = limit
		req.Offset = offset
		if res = exam_serv.QstServ.Page(req); res.Code == utils.Succeed.Code {
			dto.List = res.Data
			utils.ToJson(w, &utils.ResJson{Code: res.Code, Msg: res.Msg, Data: dto})
			return
		}
	}
	utils.ToJson(w, utils.NoData)
}

// Sort 排序
func (c *quest) Sort(r *http.Request, w http.ResponseWriter) {
	// 通过头部请求的token获取用户信息
	token := r.Header.Get(utils.Token)
	userInfo := sys_serv.GetUserInfo(token)
	if userInfo == nil {
		utils.ToJson(w, utils.NoLogin)
		return
	}
	// 过滤关键参数值中的非法字符
	u := r.URL.Query()
	if u == nil {
		utils.ToJson(w, utils.ParamErr)
		return
	}
	kinds := u.Get("kind")
	// 过滤关键参数值中的非法字符
	kinds = utils.InputFilter(kinds, true)
	kind := parse.Str2u8(kinds)
	res := exam_serv.QstServ.Sort(kind)
	utils.ToJson(w, res)
}
